package com.aaa.service.impl;

import com.aaa.service.ProductService;
import com.aaa.utils.JDHtmlParse;
import com.aaa.vo.CommonResult;
import com.aaa.vo.Product;
import com.alibaba.fastjson2.JSON;
import org.elasticsearch.action.bulk.BulkRequest;
import org.elasticsearch.action.bulk.BulkResponse;
import org.elasticsearch.action.index.IndexRequest;
import org.elasticsearch.action.search.SearchRequest;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.client.RequestOptions;
import org.elasticsearch.client.RestHighLevelClient;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
import org.elasticsearch.xcontent.XContentType;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.util.*;
import java.util.stream.Collectors;

/**
 * -*- coding:utf-8 -*-
 *
 * @author 太阳偷渡青山
 * @software IntelliJ IDEA
 * @date 2022/12/28 10:06
 * @Description
 */
@Service
public class ProductServiceImpl implements ProductService {
    @Autowired
    private RestHighLevelClient client;

    /**
     * 批量添加到ES引擎中
     *
     * @param keyword 关键字
     * @return {@link CommonResult}
     * @throws Exception 异常
     */
    @Override
    public CommonResult export(String keyword) {
        List<Product> list = null;
        try {
            list = JDHtmlParse.parse(keyword);
        } catch (Exception e) {
            e.printStackTrace();
        }

        BulkRequest bulkRequest = new BulkRequest("qy158-jd");

        for (Product product : Objects.requireNonNull(list)) {
            IndexRequest indexRequest = new IndexRequest();
            indexRequest.source(JSON.toJSONString(product), XContentType.JSON);
            bulkRequest.add(indexRequest);
        }

        BulkResponse bulkResponse = null;
        try {
            bulkResponse = client.bulk(bulkRequest, RequestOptions.DEFAULT);
        } catch (IOException e) {
            e.printStackTrace();
        }
        if(Objects.requireNonNull(bulkResponse).hasFailures()){
            return new CommonResult(5000,"批量导入商品失败",null);
        }

        return new CommonResult(2000,"批量导入商品成功",null);

    }

    @Override
    public CommonResult search(String keyword, Integer currentPage, Integer size) {

        // 1.搜索的请求对象。
        SearchRequest searchRequest = new SearchRequest("qy158-jd");

        // 2.构建一个条件类对象。
        SearchSourceBuilder sourceBuilder = new SearchSourceBuilder();

        //match匹配
        sourceBuilder.query(QueryBuilders.matchQuery("pname",keyword));
        // 分页
        if(currentPage != 0 && size != 0){
            sourceBuilder.from((currentPage - 1) * size);
            sourceBuilder.size(size);
        }

        //高亮
        HighlightBuilder highlightBuilder = new HighlightBuilder();
        highlightBuilder.preTags("<font color = 'red'>");
        highlightBuilder.postTags("</font>");
        highlightBuilder.field("pname");
        sourceBuilder.highlighter(highlightBuilder);

        // 3.把条件对象封装到searchRequest对象中。
        searchRequest.source(sourceBuilder);

        SearchResponse search = null;
        try {
            // 4.调用search执行
            search = client.search(searchRequest,RequestOptions.DEFAULT);
        } catch (IOException e) {
            e.printStackTrace();
        }

        SearchHit[] hits = Objects.requireNonNull(search).getHits().getHits();

        List<Map<String, Object>> collect = Arrays.stream(hits).map(hit -> {
            Map<String, Object> sourceAsMap = hit.getSourceAsMap();

            String pname = hit.getHighlightFields().get("pname").getFragments()[0].toString();

            sourceAsMap.put("pname",pname);

            return sourceAsMap;
        }).collect(Collectors.toList());

        Long total = search.getHits().getTotalHits().value;

        HashMap<String, Object> map = new HashMap<>();
        map.put("hits",collect);
        map.put("total",total);

        return new CommonResult(2000,keyword + "查询成功",map);
    }
}
